using CfgTable;
using IQIGame.Onigao.Framework;
using UnityEngine;

namespace IQIGame.Onigao.GamePlay
{
    public class EntityAnimationComponent : TReusableEvtComponent
    {
        public override uint MaxStore => 50;
        public AnimatorAgent animator { set; get; }

        public override void OnComponentEvent<T>(TComponentEvent eventType, T arg)
        {
            switch (eventType)
            {
                case TComponentEvent.OnEntityObjectLoaded:
                    animator = _entity.GetAnimator();
                    break;
            }
        }

        public void StartAnimAction(int actionId, float normalizedTime = 0)
        {
            if (animator == null)
            {
                return;
            }
            if (actionId <= 0)
            {
                return;
            }
            var actionCfg = TableCenter.entityAnimAction.Get(actionId);
            if (actionCfg == null)
            {
                return;
            }
            var paramHash = Animator.StringToHash(actionCfg.ActionName);

#if UNITY_EDITOR
            if (!animator.isActiveAndEnabled)
            {
                LogGame.LogWarning($"GameObject是隐藏状态，或者状态机未开启，无法播放！entity:{_entity.name}");
                return;
            }
#endif

            switch (actionCfg.ActionType)
            {
                case AniActionType.eClip:
                    float actionTime = actionCfg.TransitionDuration.MillisecToSec();
#if UNITY_EDITOR
                    if (!animator.HasState(actionCfg.Layer, paramHash))
                    {
                        LogGame.LogError($"找不到对应的动作状态,请检查配置表或状态机！entity:{_entity.name}  actionId: {actionId} actionName:{actionCfg.ActionName}");
                        break;
                    }
#endif
                    animator.CrossFade(paramHash, actionTime, actionCfg.Layer, normalizedTime);
                    break;
                case AniActionType.eTrigger:
                    animator.SetTrigger(paramHash);
                    break;
                case AniActionType.eBool:
                    animator.SetBool(paramHash, actionCfg.ActionValue != 0);
                    break;
                case AniActionType.eFloat:
                    animator.SetFloat(paramHash, actionCfg.ActionValue / 1000f);
                    break;
                case AniActionType.eInt:
                    animator.SetFloat(paramHash, actionCfg.ActionValue);
                    break;
            }
        }

        public void StopAnimAction(int actionId)
        {
            if (animator == null)
            {
                return;
            }
            var actionCfg = TableCenter.entityAnimAction.Get(actionId);
            if (actionCfg == null)
            {
                return;
            }

            var paramHash = Animator.StringToHash(actionCfg.ActionName);

            switch (actionCfg.ActionType)
            {
                case AniActionType.eBool:
                    animator.SetBool(paramHash, actionCfg.EndValue != 0);
                    break;
                case AniActionType.eFloat:
                    animator.SetFloat(paramHash, actionCfg.EndValue / 1000f);
                    break;
                case AniActionType.eInt:
                    animator.SetFloat(paramHash, actionCfg.EndValue);
                    break;
            }
        }

        public void PlayBorn()
        {
            if (animator == null)
            {
                return;
            }
            if (animator.HasState(0, AnimationConst.Name_Born))
            {
                animator.SetTrigger(AnimationConst.Param_Born);
            }
            else
            {
                animator.SetTrigger(AnimationConst.Param_Reset);
            }
        }

        public bool PlayDie()
        {
            if (animator == null)
            {
                return false;
            }
            if (!animator.HasState(0, AnimationConst.Name_Die))
            {
                return false;
            }
            animator.SetTrigger(AnimationConst.Param_Die);
            return true;
        }

        public void SetMoveSpeed(float speed)
        {
            if (animator == null)
            {
                return;
            }
            animator.SetFloat(AnimationConst.Param_Speed, speed);
        }

        public void SetJoyStickPower(float power)
        {
            if (animator == null)
            {
                return;
            }
            animator.SetFloat(AnimationConst.Param_JoyStickPower, power);
        }

        public float GetMoveSpeed()
        {
            if (animator == null)
            {
                return 0f;
            }
            return animator.GetFloat(AnimationConst.Param_Speed);
        }

        public void PlayTurnLeft()
        {
            if (animator == null)
            {
                return;
            }
            if (animator.HasState(0, AnimationConst.Name_State_TurnLeft))
            {
                animator.CrossFade(AnimationConst.Name_State_TurnLeft, AnimationConst.CommonTransitionDuration);
            }
        }

        public void PlayTurnRight()
        {
            if (animator == null)
            {
                return;
            }
            if (animator.HasState(0, AnimationConst.Name_State_TurnRight))
            {
                animator.CrossFade(AnimationConst.Name_State_TurnRight, AnimationConst.CommonTransitionDuration);
            }
        }

        public void PlayBrake()
        {
            if (animator == null)
            {
                return;
            }
            if (animator.HasState(0, AnimationConst.Name_Brake))
            {
                animator.CrossFade(AnimationConst.Name_Brake, AnimationConst.FastTransitionDuration);
            }
        }

        public void TriggerDie()
        {
            if (animator == null)
            {
                return;
            }
            animator.SetTrigger(AnimationConst.Param_Die);
        }

        public void SetStartMove(bool value)
        {
            if (animator == null)
            {
                return;
            }
            animator.SetBool(AnimationConst.Param_StartMove, value);
        }

        public void ResetAnim()
        {
            if (animator == null)
            {
                return;
            }
            animator.SetTrigger(AnimationConst.Param_Reset);
        }

        public override void OnPoolReset()
        {
            animator = null;
        }
    }
}
